
#############################
#
# 电子发票（普通发票）解析
#
#############################

from ..handle_pdf.fitz import get_info_from_rect
from .invoice import Invoice

# 电子发票（普通发票）重要信息的正则表达式
# 在电子发票（普通发票）中，重要信息包括发票号码、开票日期、小写金额，这些信息都是一直到发票右边的。
NORMAL_INVOICE_BASE_PATTRNS = {
    "invoice_number": ["发票号码", r"发票号码\s*[:：]?\s*(\d{20})"],
    "date": ["开票日期", r"开票日期\s*[:：]?\s*(\d{4}年\d{2}月\d{2}日)"],
    "amount": ["小写", r"小写[）\)]\s*[:：]?\s*([¥￥]?\s*\d+[.\.]\d{2})"],
}

# 电子发票（普通发票）购买方和销售方的正则表达式
NORMAL_INVOICE_TRADER_PATTRNS={
    "traders":["名称：",r"名称：\s*(\w+)"],
    "tax_ids":["统一社会信用代码/纳税人识别号",r"统一社会信用代码/纳税人识别号\s*[:：]?\s*([0-9A-Z]{18})"]
}

# 电子发票（普通发票）明细的正则表达式
NORMAL_INVOICE_DETAIL_PATTRNS = {
    "details": r"\*\w+",  # 明细
}

def get_normal_invoice_info_from_page(page)->dict:
    # Get the page rectangle and width
    page_rect=page.rect
    # Get the page width
    page_width=page_rect.width
    # Initialize the result dictionary
    result={}
    # get basic information
    for key,str_pattern in NORMAL_INVOICE_BASE_PATTRNS.items():
        rect=page.search_for(str_pattern[0])[0]
        if rect:
            rect[2]=page_width
            result[key] = get_info_from_rect(page,rect,str_pattern[1])
            
        else:
            return ValueError(f"Can't find {str_pattern[0]} in the page")
        
    # get trader information
    # 买卖双方的信息在发票的左半部分和右半部分
    # 左半部分是购买方，右半部分是销售方
    # 所以我们需要根据页面的宽度来判断是购买方还是销售方
    for key,str_pattern in NORMAL_INVOICE_TRADER_PATTRNS.items():
        rects=page.search_for(str_pattern[0])
        rects_answer_dict={}
        for rect in rects:
            if rect.top_left[0]>page_width/2:
                rect[2]=page_width
                rects_answer_dict["solder"]=get_info_from_rect(page,rect,str_pattern[1])
            else:
                rect[2]=page_width/2
                rects_answer_dict["buyer"]=get_info_from_rect(page,rect,str_pattern[1])

        result[key]=rects_answer_dict
    
    # get detail information
    table=page.find_tables()[0]
    # 根据表格的行和列来获取明细信息
    # 一般来讲明细信息在表格的第二行第一列
    detail_rect=table.rows[1].cells[0]
    detail_info=get_info_from_rect(page,detail_rect,NORMAL_INVOICE_DETAIL_PATTRNS["details"],"findall")
    result["details"]="".join(detail_info)
    print(result)
    return result

class NormalInvoice(Invoice):
    def __init__(self, page):
        self._invoice_info = get_normal_invoice_info_from_page(page)

    @property
    def invoice_number(self):
        return self._invoice_info.get("invoice_number", "")

    @property
    def date(self):
        return self._invoice_info.get("date", "")

    @property
    def amount(self):
        return self._invoice_info.get("amount", "")
    
    # other properties for buyer, solder, and details 
    @property
    def buyer(self):
        return self._invoice_info.get("traders", {}).get("buyer", "")

    @property
    def solder(self):
        return self._invoice_info.get("traders", {}).get("solder", "")      
    
    @property
    def details(self):
        return self._invoice_info.get("details", "")